using System;
using BenjaminSchroeter.Dsl.CompartmentMapping;
using Microsoft.VisualStudio.Modeling;
using Microsoft.VisualStudio.Modeling.Diagrams.GraphObject;

namespace BenjaminSchroeter.AdvancedCompartmentMapping
{
	#region Code for ConnectionBuilder 'BaseDataReferencesTargetBaseDatum'
    [RuleOn(typeof(Entry), FireTime = TimeToFire.LocalCommit)]
    public class SourceOrTargetOfBaseDataReferencesTargetBaseDatumDeletingRule : CompartmentEntryDeletingRuleBase<BaseData, Entry, BaseDataReferencesTargetBaseDatum, BaseData, Entry>
    {
        protected override CompartmentMappingBuilderBase<BaseData, Entry, BaseDataReferencesTargetBaseDatum, BaseData, Entry> GetBuilderInstance()
        {
            return BaseDataReferencesTargetBaseDatumBuilder.builder;
        }
    }

    public class BaseDataReferencesTargetBaseDatumRouter : CompartmentMappingRouterBase<BaseData, Entry, BaseDataReferencesTargetBaseDatum, BaseData, Entry>
    {
        protected override CompartmentMappingBuilderBase<BaseData, Entry, BaseDataReferencesTargetBaseDatum, BaseData, Entry> GetBuilderInstance()
        {
            return BaseDataReferencesTargetBaseDatumBuilder.builder;
        }
    }

    public partial class BaseDataReferencesTargetBaseDatumBuilder
    {
        internal static readonly BaseDataReferencesTargetBaseDatumBuilderInstance builder = new BaseDataReferencesTargetBaseDatumBuilderInstance();

        public static bool CanAcceptSource(ModelElement candidate)
        {
            return builder.CanAcceptSource(candidate);
        }

        public static bool CanAcceptTarget(ModelElement candidate)
        {
            return builder.CanAcceptTarget(candidate);
        }

        public static bool CanAcceptSourceAndTarget(ModelElement candidateSource, ModelElement candidateTarget)
        {
            return builder.CanAcceptSourceAndTarget(candidateSource, candidateTarget);
        }

        public static ElementLink Connect(ModelElement source, ModelElement target)
        {
            return builder.Connect(source, target);
        }
    }

	// Create this partial class in another file and implement at least the abstract methods!
    public partial class BaseDataReferencesTargetBaseDatumBuilderInstance : CompartmentMappingBuilderBase<BaseData, Entry, BaseDataReferencesTargetBaseDatum, BaseData, Entry>
    {
        internal BaseDataReferencesTargetBaseDatumBuilderInstance()
            : base(
                false,		/* connection.Source.AllowHead */
                false,		/* connection.Target.AllowHead */
                false		/* connection.AllowSelfReference */		)
        {
        }
    }	
	#endregion

	#region Code for CompartmentShape 'CompartmentShape'
    partial class CompartmentShape : ICompartmentMouseActionTrackable
    {
        private readonly CompartmentMouseTrack mouseTrack = new CompartmentMouseTrack();

        public CompartmentMouseTrack MouseTrack
        {
            get { return mouseTrack; }
        }

        public override void OnShapeInserted()
        {
            mouseTrack.ShapeInserted(this);
            base.OnShapeInserted();
        }
        
        public override void OnAbsoluteBoundsChanged(Microsoft.VisualStudio.Modeling.Diagrams.AbsoluteBoundsChangedEventArgs e)
        {
            CompartmentMappingUtil.RerouteCompartmentMappings(this);
            base.OnAbsoluteBoundsChanged(e);
        }
    }
	#endregion

	#region Code for Shape 'GeometryShape'
    partial class GeometryShape
    {
        public override void OnAbsoluteBoundsChanged(Microsoft.VisualStudio.Modeling.Diagrams.AbsoluteBoundsChangedEventArgs e)
        {
            CompartmentMappingUtil.RerouteCompartmentMappings(this);
            base.OnAbsoluteBoundsChanged(e);
        }
    }
	#endregion

	#region Code for Connector 'Connector'
    partial class Connector
    {
        public override void OnInitialize()
        {
            this.FixedFrom = VGFixedCode.Caller;
            this.FixedTo = VGFixedCode.Caller;
            base.OnInitialize();
        }

        public override bool CanManuallyRoute
        {
            get
            {
                return false;
            }
        }
    }
    
    [RuleOn(typeof(Connector), FireTime = TimeToFire.LocalCommit)]
    public class ConnectorAddRule : CompartmentMappingAddRuleBase
    {
    }
	#endregion
}
